import { IParam, UIServiceBase } from "@/core";

/**
 * 界面服务基类 
 * 基于template/src/ui-service/entity-ui-service-base.ts.hbs生成
 *
 * @export
 * @class UIService
 */
export class EntityUIServiceBase extends UIServiceBase {

  /**
   * 应用实体主键属性
   *
   * @protected
   * @type {string}
   * @memberof UIService
   */
  protected appDeKeyFieldName = '';

  /**
   * 主状态属性集合
   *
   * @memberof  UIService
   */
  protected mainStateFields: Array<string> = [];

  /**
   * 主状态集合Map
   *
   * @memberof  UIService
   */
  protected allDeMainStateMap: Map<string, string> = new Map();

  /**
   * 主状态操作标识Map
   *
   * @memberof  UIService
   */
  protected allDeMainStateOPPrivsMap: Map<string, any> = new Map();

  /**
   * 系统默认操作标识
   *
   * @protected
   * @type {IParam}
   * @memberof EntityUIServiceBase
   */
  protected sysOPPrivs: IParam = {
    {{#each app.allPSDEOPPrivs as | psDEOPPriv |}}
    '{{psDEOPPriv.name}}': '{{psDEOPPriv.mapPSSysUniRes.resCode}}',
    {{/each}}
  };

  /**
   * @description 系统操作标识映射统一资源映射表
   * @type {Map<string, string>}
   * @memberof EntityUIServiceBase
   */
  protected sysOPPrivsMap: Map<string, string> = new Map();

  /**
   * 默认操作标识 todo
   *
   * @public
   * @type {(any)}
   * @memberof EntityUIServiceBase
   */
  protected defaultOPPrivs: any = {
    {{#each app.allpsdeopprivs as | psDEOPPriv |}}
    '{{psDEOPPriv.name}}': '{{psDEOPPriv.mapPSSysUniRes.resCode}}',
    {{/each}}
  };

  /**
    * Creates an instance of EntityUIServiceBase
    * 
    * @param {*} [opts={}]
    * @memberof EntityUIServiceBase
    */
  constructor(opts: IParam = {}) {
    super();
    // 系统操作标识映射统一资源映射表
    {{#each app.allPSDEOPPrivs as | psDEOPPriv |}}
    this.sysOPPrivsMap.set('{{psDEOPPriv.name}}', '{{psDEOPPriv.mapPSSysUniRes.resCode}}');
    {{/each}}
  }

  /**
   * 应用是否启用权限
   *
   * @return {boolean} 
   * @memberof EntityUIServiceBase
   */
  protected getEnablePermission(): boolean {
    const appData = App.getAppData();
    return appData.enablepermissionvalid && App.getEnvironment().enablePermissionValid;
  }

  /**
  * 获取应用权限
  *
  * @param {string | undefined} dataAccAction 操作标识
  * @param {('RESOURCE'|'RT'|'MINIX')} [mode='RESOURCE'] RT(RT模式),RESOURCE(资源模式),MINIX(混合模式),默认值RESOURCE
  * @return {*}  {boolean}
  * @memberof EntityUIServiceBase
  */
  protected getAppAuth(dataAccAction: string | undefined, mode: 'RESOURCE' | 'RT' | 'MINIX' = 'RESOURCE'): boolean {
    if (!this.getEnablePermission() || !dataAccAction) {
      return true;
    }
    const menuAuth = App.getAppMenuAuth(dataAccAction);
    const uniresAuth = App.getAppUniresAuth(dataAccAction);
    // 资源模式
    if (Object.is(mode, 'RESOURCE')) {
      return uniresAuth;
    }
    // RT模式(菜单)
    if (Object.is(mode, 'RT')) {
      return menuAuth;
    }
    // 混合模式
    if (Object.is(mode, 'MINIX')) {
      return menuAuth && uniresAuth;
    }
    return false;
  }

  /**
   * 获取计算统一资源之后的系统操作标识
   *
   * @returns {}
   * @memberof EntityUIServiceBase
   */
  protected getSysOPPrivs() {
    const copySysOPPrivs = JSON.parse(JSON.stringify(this.defaultOPPrivs));
    if (Object.keys(copySysOPPrivs).length === 0) return {};
    Object.keys(copySysOPPrivs).forEach((name: any) => {
      if (this.sysOPPrivsMap.get(name)) {
        copySysOPPrivs[name] = this.getResourcePermission(this.sysOPPrivsMap.get(name)) ? 1 : 0;
      }
    })
    return copySysOPPrivs;
  }

  /**
   * 根据统一资源标识获取统一资源权限
   *
   * @param {*} tag 统一资源标识
   * @returns {boolean}
   * @memberof EntityUIServiceBase
   */
  protected getResourcePermission(tag: any): boolean {
    if (!App.getEnableAppPermission()) {
      return true;
    }
    return App.getAppUniresAuth(tag);
  }

  /**
   *
   *
   * @param {string} tag
   * @param {IParam} data
   * @return {*}  {(1 | 2 | 3)} 有权限 | 禁用 | 不显示
   * @memberof EntityUIServiceBase
   */
  public getOPPrivsAuth(tag: string, data: IParam): 1 | 2 | 3 {
    const Environment = App.getEnvironment();
    if (!Environment.enablePermissionValid) {
      return 1;
    }
    if (data && (Object.keys(data).length > 0)) {
      const curActiveKey = `${data[this.appDeKeyFieldName?.toLowerCase()]}`;
      const result = this.getOPPrivs(curActiveKey, tag, this.getDEMainStateOPPrivs(data));
      return result[tag];
    } else {
      const result = this.getOPPrivs(undefined, tag, undefined);
      return result[tag];
    }
  }

  /**
   * 根据当前数据获取实体操作标识
   *
   * @param {*} activeKey 实体权限数据缓存标识
   * @param {*} dataaccaction 操作标识
   * @param {*} mainSateOPPrivs 传入数据主状态操作标识集合
   * @returns {any}
   * @memberof EntityUIServiceBase
   */
  protected getOPPrivs(activeKey = '', dataaccaction: string, mainSateOPPrivs: any): any {
    const result = { [dataaccaction]: 1 };
    const curDefaultOPPrivs: any = this.getSysOPPrivs();
    // 统一资源权限
    if (curDefaultOPPrivs && (Object.keys(curDefaultOPPrivs).length > 0) && (curDefaultOPPrivs[dataaccaction] === 0)) {
      result[dataaccaction] = 0;
    }
    // 主状态权限
    if (mainSateOPPrivs && (Object.keys(mainSateOPPrivs).length > 0) && mainSateOPPrivs.hasOwnProperty(dataaccaction)) {
      result[dataaccaction] = result[dataaccaction] && mainSateOPPrivs[dataaccaction];
    }
    // 实体级权限
    if (!this.getDEAuth(activeKey, dataaccaction)) {
      result[dataaccaction] = 0;
    }
    return result;
  }

  /**
   * 获取数据对象当前操作标识
   *
   * @param data 当前数据
   * @memberof  EntityUIServiceBase
   */
  protected getDEMainStateOPPrivs(data: any) {
    if (this.getDEMainStateTag(data)) {
      return this.allDeMainStateOPPrivsMap.get(this.getDEMainStateTag(data) as string);
    } else {
      return null;
    }
  }

  /**
  * 获取数据对象的主状态标识
  *
  * @param curData 当前数据
  * @memberof  EntityUIServiceBase
  */
  protected getDEMainStateTag(curData: any) {
    if (this.mainStateFields.length === 0) return null;
    this.mainStateFields.forEach((singleMainField: any) => {
      if (!(singleMainField in curData)) {
        console.warn(
          `当前数据对象不包含属性「${singleMainField}」，根据「${singleMainField}」属性进行的主状态计算默认为空值`,
        );
      }
    });
    for (let i = 0; i <= 1; i++) {
      const strTag: string =
        curData[this.mainStateFields[0]] != null && curData[this.mainStateFields[0]] !== ''
          ? i == 0
            ? `${curData[this.mainStateFields[0]]}`
            : ''
          : '';
      if (this.mainStateFields.length >= 2) {
        for (let j = 0; j <= 1; j++) {
          const strTag2: string =
            curData[this.mainStateFields[1]] != null && curData[this.mainStateFields[1]] !== ''
              ? `${strTag}__${j == 0 ? `${curData[this.mainStateFields[1]]}` : ''}`
              : strTag;
          if (this.mainStateFields.length >= 3) {
            for (let k = 0; k <= 1; k++) {
              const strTag3: string =
                curData[this.mainStateFields[2]] != null && curData[this.mainStateFields[2]] !== ''
                  ? `${strTag2}__${k == 0 ? `${curData[this.mainStateFields[2]]}` : ''}`
                  : strTag2;
              // 判断是否存在
              return this.allDeMainStateMap.get(strTag3);
            }
          } else {
            return this.allDeMainStateMap.get(strTag2);
          }
        }
      } else {
        return this.allDeMainStateMap.get(strTag);
      }
    }
    return null;
  }


  /**
   * 获取实体级数据操作标识
   *
   * @param {*} key 缓存主键
   * @param {*} dataaccaction 操作标识
   * @returns {}
   * @memberof EntityUIServiceBase
   */
  public getDEAuth(key: string, dataaccaction: string): boolean {
    return true
  }
}
